home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 10 / AACD 10.iso / AACD / Magazine / Online / MagPLIP / source / magport.asm < prev    next >
Assembly Source File  |  1998-04-01  |  11KB  |  346 lines

  1. ;
  2. ;  $VER: port.asm 1.7 (21 Feb 1998)
  3. ;
  4. ;  magplip.device - Parallel Line Internet Protocol
  5. ;
  6. ;  Assembler routines for efficient port handling.
  7. ;
  8. ;  Original code written by Oliver Wagner and Michael Balzer.
  9. ;
  10. ;  This version has been completely reworked by Marius Gröger, introducing
  11. ;  slight protocol changes. The new source is a lot better organized and
  12. ;  maintainable.
  13. ;
  14. ;  Additional changes and code cleanup by Jan Kratochvil and Martin Mares.
  15. ;  The new source is significantly faster and yet better maintainable.
  16. ;
  17. ;  (C) Copyright 1993-1994 Oliver Wagner & Michael Balzer
  18. ;  (C) Copyright 1995 Jan Kratochvil & Martin Mares
  19. ;  (C) Copyright 1995-1996 Marius Gröger
  20. ;      All Rights Reserved
  21. ;
  22. ;  $HISTORY:
  23. ;
  24. ;  21 Feb 1998 : 001.007 :  added SysBase to A6 in the interrupt handler
  25. ;  29 Mar 1996 : 001.006 :  changed copyright note
  26. ;  24 Feb 1996 : 001.005 :  + added PRTRSEL data direction signal
  27. ;                           + minor re-arrangements
  28. ;  30 Dec 1995 : 001.004 :  support for single frame buffer
  29. ;  05 Dec 1995 : 001.003 :  + short branches explicitly coded as such
  30. ;                           + some condition jumps which were effectively
  31. ;                             unconditional changed to bra's
  32. ;  30 Aug 1995 : 001.002 :  support for timer-timed timeout :-)
  33. ;  20 Aug 1995 : 001.001 :  + removed need for conditional compiling, as we
  34. ;                             we want a generic, symmetrical code
  35. ;                           + in interrupt handlers, A6 points already to
  36. ;                             SysBase
  37. ;                           + using JSRLIB/JMPLIB macros
  38. ;                           + removed implicit some assumptions on the values
  39. ;                             behind symbolic names
  40. ;  13 Feb 1995 : 001.000 :  created (in fact manually compiled from 'C'-
  41. ;                           original) (jk/mm)
  42. ;
  43.       section "text",code
  44.  
  45.  
  46. ;----------------------------------------------------------------------------
  47.  
  48.  
  49.       IFND HARDARE_CIA_I
  50.       include "hardware/cia.i"
  51.       ENDC
  52.  
  53.       IFND EXEC_MACROS_I
  54.       include "exec/macros.i"
  55.       ENDC
  56.  
  57.       IFND MAGPLIP_I
  58.       include "magplip.i"
  59.       ENDC
  60.  
  61.  
  62. ;----------------------------------------------------------------------------
  63.  
  64.  
  65.       xref    _CRC16
  66.  
  67.       xdef    _interrupt
  68.       xdef    _hwsend
  69.       xdef    _hwrecv
  70.  
  71. ;----------------------------------------------------------------------------
  72.  
  73. ciaa     equ     $bfe001
  74. ciab     equ     $bfd000
  75. BaseAX   equ     ciab+ciapra
  76.  
  77.  
  78. SETCIAOUTPUT MACRO
  79.       bset     #CIAB_PRTRSEL,ciab+ciapra-BaseAX(a5)   ; raise PRTSEL line
  80.       st       ciaa+ciaddrb-BaseAX(\1)                ; data dir. => output
  81.       ENDM
  82.  
  83. SETCIAINPUT MACRO
  84.       bclr     #CIAB_PRTRSEL,ciab+ciapra-BaseAX(a5)   ; lower PRTSEL line
  85.       sf       ciaa+ciaddrb-BaseAX(\1)                ; data dir. => input
  86.       ENDM
  87.  
  88.  
  89. ;----------------------------------------------------------------------------
  90. ;
  91. ; NAME
  92. ;     interrupt() - ICR FLG interrupt server
  93. ;
  94. ; SYNOPSIS
  95. ;     void interrupt(struct PLIPBase *)
  96. ;                    A1
  97. ;
  98. ; FUNCTION
  99. ;     This is called from CIA resource on the receipt of an parallel port
  100. ;     FLG line interrupt. This is the case if the other side starts
  101. ;     transmission and writes the first byte to our port.
  102. ;
  103. ;     We recognise this here and propagate the information to the server
  104. ;     task by Signal()ing it and by setting the PLIPB_RECEIVING bit
  105. ;     in the flags field.
  106. ;
  107. _interrupt:
  108.     btst    #PLIPB_RECEIVING,pb_Flags(a1)
  109.     bne.s   skipint
  110.     move.b  pb_HandshakeBit+HS_LINE(a1),d0
  111.     btst    d0,ciab+ciapra
  112.     beq.s   skipint
  113.     bset    #PLIPB_RECEIVING,pb_Flags(a1)
  114.     move.l  pb_IntSigMask(a1),d0
  115.     move.l  pb_SysBase(a1),a6
  116.     move.l  pb_Server(a1),a1
  117.     JSRLIB  Signal
  118. skipint:
  119.     moveq #0,d0
  120.     rts
  121.  
  122. ;----------------------------------------------------------------------------
  123. ;
  124. ; NAME
  125. ;     hwsend() - low level send routine
  126. ;
  127. ; SYNOPSIS
  128. ;     void hwsend(struct PLIPBase *)
  129. ;                  A0
  130. ;
  131. ; FUNCTION
  132. ;     This routine sends the PLIPBase->pb_Frame to the other side. It
  133. ;     cares for CRC encoding, if wanted. The frame header will be
  134. ;     set up except of the pf_Size field, which must be pre-initialized.
  135. ;
  136. _hwsend:
  137.      movem.l  d2-d7/a2-a6,-(sp)
  138.      move.l   a0,a2                               ; a2 = PLIPBase
  139.      moveq    #FALSE,d2                           ; d2 = return value
  140.      moveq    #0,d3
  141.      move.l   d3,d4
  142.      move.b   pb_HandshakeBit+HS_REQUEST(a2),d3   ; d3 = HS_REQUEST
  143.      move.b   pb_HandshakeBit+HS_LINE(a2),d4      ; d4 = HS_LINE
  144.      move.l   pb_Frame(a2),a4                     ; a4 = Frame
  145.  
  146.      ;
  147.      ; CRC wanted ?
  148.      ;
  149.      btst     #PLIPB_SENDCRC,pb_Flags(a2)
  150.      beq.s    hww_NoCRC
  151.      ; yes
  152.      move.w   #SYNCWORD_CRC,pf_Sync(a4)
  153.      lea      PLIPFrame_SIZE(a4),a0
  154.      move.w   pf_Size(a4),d0
  155.      subq.w   #PKTFRAMESIZE_2,d0
  156.      jsr      _CRC16(pc)
  157.      move.w   d0,pf_CRC(a4)
  158.      bra.s    hww_CRC
  159.  
  160. hww_NoCRC:
  161.      move.w   #SYNCWORD_NOCRC,pf_Sync(a4)
  162.  
  163. hww_CRC  move.l   pb_CIAABase(a2),a6
  164.      moveq    #CIAICRF_FLG,d0
  165.      JSRLIB   AbleICR                             ; DISABLEINT
  166.      lea      BaseAX,a5
  167.      SETCIAOUTPUT a5
  168.      move.b   (a5),d7                             ; SAMPLEINPUT, d7 = State
  169.      move.l   a4,a3
  170.      move.w   pf_Size(a4),d6
  171.      addq.w   #PKTFRAMESIZE_1-2,d6
  172.      move.b   (a3)+,ciaa+ciaprb-BaseAX(a5)        ; WRITECIA *p++
  173. hww_LoopShake1:
  174.      move.b   (a5),d0                             ; ciab+ciapra
  175.      eor.b    d7,d0
  176.      btst     d4,d0                               ; WAITINPUTTOGGLE
  177.      bne.s    hww_cont1
  178.      tst.b    pb_TimeoutSet(a2)
  179.      beq.s    hww_LoopShake1
  180.      bra.s    hww_TimedOut
  181. hww_cont1:
  182.      eor.b    d0,d7
  183.  
  184. hww_MainLoop:
  185.      move.b   (a3)+,ciaa+ciaprb-BaseAX(a5)        ; WRITECIA *p++
  186.      bchg     d3,(a5)                             ; OUTPUTTOGGLE
  187. hww_LoopShake2:
  188.      move.b   (a5),d0                             ; ciab+ciapra
  189.      eor.b    d7,d0
  190.      btst     d4,d0                               ; WAITINPUTTOGGLE
  191.      bne.s    hww_cont2
  192.      tst.b    pb_TimeoutSet(a2)
  193.      beq.s    hww_LoopShake2
  194.      bra.s    hww_TimedOut
  195. hww_cont2:
  196.      eor.b    d0,d7
  197.      dbra     d6,hww_MainLoop
  198.      moveq    #TRUE,d2                            ; rc = TRUE
  199. hww_TimedOut:
  200.      SETCIAINPUT a5
  201.      bclr     d3,(a5)                             ; CLEARREQUEST ciab+ciapra
  202.      moveq    #CIAICRF_FLG,d0
  203.      JSRLIB   SetICR                              ; CLEARINT
  204.      move.w   #CIAICRF_FLG|CIAICRF_SETCLR,d0
  205.      JSRLIB   AbleICR                             ; ENABLEINT
  206.  
  207.      move.l   d2,d0                               ; return rc
  208.      movem.l  (sp)+,d2-d7/a2-a6
  209. Return   rts
  210.  
  211.  
  212. ;----------------------------------------------------------------------------
  213. ;
  214. ; NAME
  215. ;     hwrecv() - low level receive routine
  216. ;
  217. ; SYNOPSIS
  218. ;     void hwrecv(struct PLIPBase *)
  219. ;                 A0
  220. ;
  221. ; FUNCTION
  222. ;     This routine receives a magPLIP frame and stores it into
  223. ;     PLIPBase->pb_Frame. It cares for CRC decoding, if the incoming
  224. ;     packet is encoded. The pf_Size field will indicate the length
  225. ;     of the received data.
  226. ;
  227. _hwrecv:
  228.      movem.l  d2-d7/a2-a6,-(sp)
  229.      move.l   a0,a2                               ; a2 = PLIPBase
  230.      moveq    #FALSE,d5                           ; d5 = return value
  231.      move.l   pb_CIAABase(a2),a6                  ; a6 = CIABase
  232.      moveq    #0,d3
  233.      move.l   d3,d2
  234.      move.b   pb_HandshakeBit+HS_REQUEST(a2),d3   ; d3 = HS_REQUEST
  235.      move.b   pb_HandshakeBit+HS_LINE(a2),d2      ; d2 = HS_LINE
  236.      lea      BaseAX,a5                           ; a5 = ciab+ciapra
  237.      move.l   pb_Frame(a2),a4                     ; a4 = Frame
  238.  
  239.      moveq    #CIAICRF_FLG,d0
  240.      JSRLIB   AbleICR                             ; DISABLEINT
  241.  
  242.      move.b   (a5),d7                             ; SAMPLEINPUT
  243.      cmp.b    #SYNCBYTE_HEAD,ciaa+ciaprb-BaseAX(a5) ; READCIABYTE
  244.      bne      hwr_TimedOut
  245.  
  246.      bchg     d3,(a5)                             ; OUTPUTTOGGLE
  247. hwr_LoopShake1:
  248.      move.b   (a5),d0                             ; ciab+ciapra
  249.      eor.b    d7,d0
  250.      btst     d2,d0                               ; WAITINPUTTOGGLE
  251.      bne.s    hwr_cont1
  252.      tst.b    pb_TimeoutSet(a2)
  253.      beq.s    hwr_LoopShake1
  254.      bra      hwr_TimedOut
  255. hwr_cont1:
  256.      eor.b    d0,d7
  257.      move.b   ciaa+ciaprb-BaseAX(a5),d4           ; READCIABYTE
  258.      bchg     d3,(a5)                             ; OUTPUTTOGGLE
  259.      move.b   d4,d0
  260.      subq.b   #SYNCBYTE_CRC,d0
  261.      bcs.s    hwr_TimedOut
  262.      subq.b   #SYNCBYTE_NOCRC,d0
  263.      bcc.s    hwr_TimedOut
  264.      lea      pf_Size(a4),a3
  265.  
  266.      ; Read 1st length byte
  267.      ;
  268. hwr_LoopShake2
  269.      move.b   (a5),d0                             ; ciab+ciapra
  270.      eor.b    d7,d0
  271.      btst     d2,d0                               ; WAITINPUTTOGGLE
  272.      bne.s    hwr_cont2
  273.      tst.b    pb_TimeoutSet(a2)
  274.      beq.s    hwr_LoopShake2
  275.      bra.s    hwr_TimedOut
  276. hwr_cont2:
  277.      eor.b    d0,d7
  278.      move.b   ciaa+ciaprb-BaseAX(a5),(a3)+        ; READCIABYTE
  279.      bchg     d3,(a5)                             ; OUTPUTTOGGLE
  280.  
  281.      ; Read 2nd length byte
  282.      ;
  283. hwr_LoopShake3:
  284.      move.b   (a5),d0                             ; ciab+ciapra
  285.      eor.b    d7,d0
  286.      btst     d2,d0                               ; WAITINPUTTOGGLE
  287.      bne.s    hwr_cont3
  288.      tst.b    pb_TimeoutSet(a2)
  289.      beq.s    hwr_LoopShake3
  290.      bra.s    hwr_TimedOut
  291. hwr_cont3:
  292.      eor.b    d0,d7
  293.      move.b   ciaa+ciaprb-BaseAX(a5),(a3)+        ; READCIABYTE
  294.      bchg     d3,(a5)                             ; OUTPUTTOGGLE ciab+ciapra
  295.  
  296.      move.w   -2(a3),d6                           ; = length
  297.      subq.w   #PKTFRAMESIZE_2,d6
  298.      bcs.s    hwr_TimedOut
  299.      cmp.w    pb_MTU+2(a2),d6
  300.      bhi.s    hwr_TimedOut
  301.      addq.w   #PKTFRAMESIZE_2-1,d6
  302.  
  303.      ; Read main packet body
  304.      ;
  305. hwr_MainLoop:
  306. hwr_LoopShake4:
  307.      move.b   (a5),d0                             ; ciab+ciapra
  308.      eor.b    d7,d0
  309.      btst     d2,d0
  310.      bne.s    hwr_cont4
  311.      tst.b    pb_TimeoutSet(a2)
  312.      beq.s    hwr_LoopShake4
  313.      bra.s    hwr_TimedOut
  314. hwr_cont4:
  315.      eor.b    d0,d7
  316.      move.b   ciaa+ciaprb-BaseAX(a5),(a3)+        ; READCIABYTE
  317.      bchg     d3,(a5)                             ; OUTPUTTOGGLE ciab+ciapra
  318.      dbra     d6,hwr_MainLoop
  319.  
  320. hwr_DoneRead:
  321.      subq.b   #SYNCBYTE_CRC,d4
  322.      bne.s    hwr_ReadOkay
  323.      lea      PLIPFrame_SIZE(a4),a0
  324.      move.w   pf_Size(a4),d0
  325.      subq.w   #PKTFRAMESIZE_2,d0
  326.      jsr      _CRC16(pc)
  327.      cmp.w    pf_CRC(a4),d0
  328.      bne.s    hwr_TimedOut
  329.  
  330. hwr_ReadOkay:
  331.      moveq    #TRUE,d5
  332. hwr_TimedOut:
  333.      bclr     #PLIPB_RECEIVING,pb_Flags(a2)
  334.      SETCIAINPUT a5
  335.      bclr     d3,(a5)                             ; CLEARREQUEST ciab+ciapra
  336.      moveq    #CIAICRF_FLG,d0
  337.      JSRLIB   SetICR                              ; CLEARINT
  338.      move.w   #CIAICRF_FLG|CIAICRF_SETCLR,d0
  339.      JSRLIB   AbleICR                             ; ENABLEINT
  340.  
  341.      move.l   d5,d0                               ; return value
  342.      movem.l  (sp)+,d2-d7/a2-a6
  343.      rts
  344.  
  345.      end
  346.